package com.witframework.webroot.framework.webresource.components.jmesa;

import static org.jmesa.facade.TableFacadeFactory.createTableFacade;
import static org.jmesa.limit.ExportType.CSV;
import static org.jmesa.limit.ExportType.JEXCEL;
import static org.jmesa.limit.ExportType.PDF;

import java.util.Date;
import java.util.List;

import org.jmesa.core.filter.DateFilterMatcher;
import org.jmesa.core.filter.MatcherKey;
import org.jmesa.facade.TableFacade;
import org.jmesa.limit.Limit;
import org.jmesa.view.component.Column;
import org.jmesa.view.component.Row;
import org.jmesa.view.component.Table;
import org.jmesa.view.editor.BasicCellEditor;
import org.jmesa.view.editor.CellEditor;
import org.jmesa.view.editor.DateCellEditor;
import org.jmesa.view.html.HtmlBuilder;
import org.jmesa.view.html.component.HtmlColumn;
import org.jmesa.view.html.component.HtmlRow;
import org.jmesa.view.html.component.HtmlTable;
import org.jmesa.view.html.editor.DroplistFilterEditor;

import com.witframework.baseapp.security.BaseUser;
import com.witframework.baseapp.security.BaseUser;
import com.witframework.core.WitFrameWork;
import com.witframework.core.logic.IBaseService;
import com.witframework.web.mvc.WebContext;

public class BasicController {
	private IBaseService getUserService() {
		return WitFrameWork.getSimpleBaseService(BaseUser.class);
	}

	public String executor(WebContext webContext) {
		List<BaseUser> appList = getUserService().findBy(webContext.getFilter());

		TableFacade tableFacade = createTableFacade("user", webContext.getHttpRequest());
		tableFacade.setItems(appList); // set the items
		tableFacade.setExportTypes(webContext.getHttpResponse(), CSV, JEXCEL, PDF); // set the exports allowed
		tableFacade.setStateAttr("restore"); // return to the table in the same state that the user left it.

		Limit limit = tableFacade.getLimit();
		if (limit.isExported()) {
			export(tableFacade);
			return null; // In Spring returning null tells the controller not to do anything.
		}

		String html = html(tableFacade);
		webContext.setAttribute("presidents", html); // Set the Html in the request for the JSP.
		
		return "controller:/basic.jsp";
	}

	private String html(TableFacade tableFacade) {
		// add a custom filter matcher to be the same pattern as the cell editor used.
		tableFacade.addFilterMatcher(new MatcherKey(Date.class, "birthday"), new DateFilterMatcher("yyyy-MM-dd"));

		// set the column properties
		tableFacade.setColumnProperties("firstName", "lastName", "username", "password", "birthday");

		HtmlTable table = (HtmlTable) tableFacade.getTable();
		table.setCaption("Presidents");
		table.getTableRenderer().setWidth("800px");

		HtmlRow row = table.getRow();

		HtmlColumn firstName = row.getColumn("firstName");
		firstName.setTitle("First Name");

		HtmlColumn lastName = row.getColumn("lastName");
		lastName.setTitle("Last Name");

		HtmlColumn career = row.getColumn("username");
		career.getFilterRenderer().setFilterEditor(new DroplistFilterEditor());

		Column born = row.getColumn("birthday");
		born.getCellRenderer().setCellEditor(new DateCellEditor("yyyy-MM-dd"));
		
		// Using an anonymous class to implement a custom editor.
		firstName.getCellRenderer().setCellEditor(new CellEditor() {
			public Object getValue(Object item, String property, int rowcount) {
				Object value = new BasicCellEditor().getValue(item, property, rowcount);
				HtmlBuilder html = new HtmlBuilder();
				html.a().href().quote().append("#").quote().close();
				html.append(value);
				html.aEnd();
				return html.toString();
			}
		});
		return tableFacade.render(); // Return the Html.
	}

	private void export(TableFacade tableFacade) {
		// set the column properties
		tableFacade.setColumnProperties("firstName", "lastName", "username", "password");
		Table table = tableFacade.getTable();
		table.setCaption("Presidents");
		Row row = table.getRow();
		Column firstName = row.getColumn("firstName");
		firstName.setTitle("First Name");
		Column lastName = row.getColumn("lastName");
		lastName.setTitle("Last Name");
		tableFacade.render(); // Will write the export data out to the response.
	}	
}
